package com.netx.generics.util;
import com.netx.generics.translation.TranslationStep;
import com.netx.generics.translation.Results;
import com.netx.generics.basic.IntegrityException;
import java.util.List;
import java.util.ArrayList;
import java.util.Iterator;


public class BuiltinAnalyzer extends TranslationStep {

	public BuiltinAnalyzer(BuiltinParser parser) {
		super(parser);
	}

	public Object performWork(Results r) {
		SymbolExpression expr = (SymbolExpression)r.getContents();
		StringBuilder sb = new StringBuilder();
		Iterator<BuiltinSymbol> itCalls = expr.contents.iterator();
		while(itCalls.hasNext()) {
			sb.append(_evaluate(r, itCalls.next()));
		}
		return sb.toString();
	}

	private String _evaluate(Results r, BuiltinSymbol se) {
		if(se instanceof SymbolConstant) {
			return ((SymbolConstant)se).getValue();
		}
		else if(se instanceof SymbolText) {
			return ((SymbolText)se).getText();
		}
		else if(se instanceof SymbolFunction) {
			SymbolFunction sf = (SymbolFunction)se;
			List<String> args = new ArrayList<String>();
			for(BuiltinSymbol sa : sf.arguments) {
				args.add(_evaluate(r, sa));
			}
			try {
				return Builtins.call(sf.getFunctionName(), args.toArray(new String[0]));
			}
			catch(BuiltinCallException bce) {
				r.addError(bce.getMessage(), sf.function);
				return "";
			}
		}
		else if(se instanceof SymbolSum) {
			StringBuilder sb = new StringBuilder();
			for(BuiltinSymbol ss : ((SymbolSum)se).operands) {
				sb.append(_evaluate(r, ss));
			}
			return sb.toString();
		}
		else {
			throw new IntegrityException(se);
		}
	}
}
